/*
 * MIT License
 *
 * Copyright (c) 2023 北京凯特伟业科技有限公司
 *
 * Permission is hereby granted, free of charge, to any person obtaining a copy
 * of this software and associated documentation files (the "Software"), to deal
 * in the Software without restriction, including without limitation the rights
 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
 * copies of the Software, and to permit persons to whom the Software is
 * furnished to do so, subject to the following conditions:
 *
 * The above copyright notice and this permission notice shall be included in all
 * copies or substantial portions of the Software.
 *
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
 * SOFTWARE.
 */
package com.je.meta.controller.setting;

import com.alibaba.fastjson2.JSON;
import com.alibaba.fastjson2.JSONObject;
import com.google.common.base.Strings;
import com.google.common.collect.Lists;
import com.je.auth.check.annotation.AuthCheckPermission;
import com.je.common.base.DynaBean;
import com.je.common.base.constants.message.SendContextType;
import com.je.common.base.mvc.AbstractPlatformController;
import com.je.common.base.result.BaseRespResult;
import com.je.common.base.util.StringUtil;
import com.je.ibatis.extension.conditions.ConditionsWrapper;
import com.je.message.rpc.EmailRpcServiceImpl;
import com.je.meta.cache.setting.SystemDecryptCache;
import com.je.meta.cache.variable.FrontCache;
import com.je.meta.service.setting.MetaSystemSettingService;
import com.je.meta.service.variable.MetaSysVariablesService;
import com.je.meta.setting.SettingException;
import com.je.meta.setting.SystemSetting;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RestController;

import javax.servlet.http.HttpServletRequest;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

@RestController
@RequestMapping(value = "/je/meta/setting")
public class SystemSettingController extends AbstractPlatformController {
    private static final Logger logger = LoggerFactory.getLogger(SystemSettingController.class);
    private static final String SETTING_ATTRIBUTE = "attribute";

    @Autowired
    private MetaSystemSettingService metaSystemConfigService;
    @Autowired
    private EmailRpcServiceImpl emailRpcService;
    @Autowired
    private SystemDecryptCache systemDecryptCache;
    @Autowired
    private FrontCache frontCache;
    @Autowired
    private MetaSysVariablesService metaSysVariablesService;

    @RequestMapping(value = "/loadFrontendSetting", method = RequestMethod.POST, produces = "application/json; charset=utf-8")
    public BaseRespResult loadFrontendSetting(HttpServletRequest request) {
        List<DynaBean> settingList = metaService.select("JE_CORE_SETTING", ConditionsWrapper.builder()
                .in("ATTRIBUTE", Lists.newArrayList("document-setting", "security-config", "runtime-config", "develop-online", "login-config")));
        Map<String, Object> values = new HashMap<>();
        for (DynaBean eachBean : settingList) {
            values.put(eachBean.getStr("CODE"), eachBean.getStr("VALUE"));
        }

        //系统变量,不要合并到values里面，特意拆开
        Map<String, String> frontVar = frontCache.getCacheValues();
        if (null == frontVar || frontVar.size() == 0) {
            metaSysVariablesService.reloadSystemVariables();
            frontVar = frontCache.getCacheValues();
        }
        values.put("variables", frontVar);
        return BaseRespResult.successResult(values);
    }

    /**
     * 获取系统设置管理(前端用)前端加载主页会调用
     */
    @RequestMapping(value = "/loadSystemSetting", method = RequestMethod.POST, produces = "application/json; charset=utf-8")
    public BaseRespResult loadSystemSetting(HttpServletRequest request) {
        String attribute = getStringParameter(request, SETTING_ATTRIBUTE);
        if (Strings.isNullOrEmpty(attribute)) {
            return BaseRespResult.errorResult("请选择要加载的配置属性！");
        }
        SystemSetting systemSetting = metaSystemConfigService.findSystemConfig(attribute);
        if (systemSetting == null) {
            return BaseRespResult.errorResult("不存在此系统设置集合");
        }
        return BaseRespResult.successResult(systemSetting);
    }

    /**
     * 重新加载配置
     */
    @RequestMapping(value = "/reloadSetting", method = RequestMethod.POST, produces = "application/json; charset=utf-8")
    public BaseRespResult reloadSetting() {
        metaSystemConfigService.reloadLoadSystemSetting();
        return BaseRespResult.successResult("重置缓存成功！");
    }

    /**
     * 加载系统设置(系统设置页面回显使用)
     */
    @RequestMapping(value = "/selectSystemConfig", method = RequestMethod.POST, produces = "application/json; charset=utf-8")
    public BaseRespResult selectSystemConfig(HttpServletRequest request) {
        String attribute = getStringParameter(request, SETTING_ATTRIBUTE);
        if (Strings.isNullOrEmpty(attribute)) {
            return BaseRespResult.errorResult("请选择要加载的配置属性！");
        }
        SystemSetting systemSetting = metaSystemConfigService.findSystemConfig(attribute);
        return BaseRespResult.successResult(systemSetting);
    }

    /**
     * 更新系统设置(系统设置页面保存使用)
     */
    @AuthCheckPermission(value = "pc-plugin-JE_CORE_SETTINGS_*-show")
    @RequestMapping(value = "/writeSysVariables", method = RequestMethod.POST, produces = "application/json; charset=utf-8")
    public BaseRespResult writeSysVariables(HttpServletRequest request) {
        String attribute = getStringParameter(request, SETTING_ATTRIBUTE);
        String type = getStringParameter(request, "type");
        if (Strings.isNullOrEmpty(attribute)) {
            return BaseRespResult.errorResult("请选择要加载的配置属性！");
        }
        String allFields = getStringParameter(request, "allFields");
        JSONObject value = JSON.parseObject(allFields);
        try {
            //安全设置
            if ("security-config".equals(attribute)) {
                Map<String, String> cacheMap = new HashMap<>();
                for (String eachKey : value.keySet()) {
                    cacheMap.put(eachKey, value.getString(eachKey));
                }
                systemDecryptCache.putMapCache(cacheMap);
            }
            metaSystemConfigService.doWriteSysConfigVariables(attribute, value, type);
        } catch (SettingException e) {
            return BaseRespResult.errorResult(e.getMessage());
        }

        return BaseRespResult.successResult(null);
    }

    /**
     * 发送邮件
     *
     * @return
     */
    @RequestMapping(value = "/sendeEmail", method = RequestMethod.POST, produces = "application/json; charset=utf-8")
    public BaseRespResult sendeEmail(HttpServletRequest request) {
        String address = getStringParameter(request, "address");
        if (StringUtil.isEmpty(address)) {
            return BaseRespResult.errorResult("发送邮箱为空！");
        }
        String content = getStringParameter(request, "content");
        logger.info("email ----------接受邮箱:   " + address);
        logger.info("email ----------内容:   " + content);
        try {
            emailRpcService.sendEmail(address, "测试发送服务器设置", SendContextType.HTML, content);
        } catch (Exception e) {
            e.printStackTrace();
            return BaseRespResult.errorResult(e.getMessage());
        }
        return BaseRespResult.successResult(null);
    }

    /**
     * 发送邮件
     *
     * @return
     */
    @RequestMapping(value = "/getMessageType", method = RequestMethod.POST, produces = "application/json; charset=utf-8")
    public BaseRespResult getMessageType(HttpServletRequest request) {
        try {
            return BaseRespResult.successResult(metaSystemConfigService.getMessageType());
        } catch (Exception e) {
            e.printStackTrace();
        }
        return BaseRespResult.errorResult(null);
    }


}
